Skip to content

Actions: Add new models for external actions/workflows - #22263

Open
JarLob wants to merge 10 commits into
github:mainfrom
JarLob:feature/actions-external-workflow-models
Open

Actions: Add new models for external actions/workflows#22263
JarLob wants to merge 10 commits into
github:mainfrom
JarLob:feature/actions-external-workflow-models

Conversation

@JarLob

@JarLob JarLob commented Jul 31, 2026

Copy link
Copy Markdown
Contributor

Previously it wasn't using extension predicates, just looking for downloaded workflow files in .github/workflows/external/. It is used only internally, so imho the accidental rename in #18563 is safe to be edited.

I used a random unique name 9466014afba34ef28239871ceabf4132 where the downloaded external workflows/actions are stored, but I'm open for discussion. The name is visible in alerts, but using something as reusable_workflows may potentially run into the naming conflict.

Copilot AI review requested due to automatic review settings July 31, 2026 09:28
@JarLob
JarLob requested a review from a team as a code owner July 31, 2026 09:28
@github-actions github-actions Bot added documentation Actions Analysis of GitHub Actions labels Jul 31, 2026

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Adds version-aware modeling and interprocedural analysis for downloaded external reusable workflows and composite actions.

Changes:

  • Adds external workflow/action extension predicates and call resolution.
  • Moves downloaded files under a collision-resistant UUID directory.
  • Adds documentation, models, and regression tests.
Show a summary per file
File Description
docs/codeql/codeql-language-guides/customizing-library-models-for-actions.rst Documents new predicates.
actions/ql/test/query-tests/Security/CWE-829/UntrustedCheckoutCritical.expected Updates expected external-workflow paths.
actions/ql/test/query-tests/Security/CWE-829/9466014afba34ef28239871ceabf4132/TestOrg/TestRepo/ref-07cp61dt7qne3/.github/workflows/reusable.yml Adds reusable-workflow fixture.
actions/ql/test/query-tests/Security/CWE-829/9466014afba34ef28239871ceabf4132/TestOrg/TestRepo/ref-07cp61dt7qne3/.github/workflows/formal.yml Adds external workflow fixture.
actions/ql/test/query-tests/Security/CWE-829/9466014afba34ef28239871ceabf4132/TestOrg/TestRepo/ref-07cp61dt7qne3/.github/workflows/build.yml Adds checkout fixture.
actions/ql/test/query-tests/Security/CWE-829/9466014afba34ef28239871ceabf4132/TestOrg/TestRepo/ref-07cp61dt7qne3/.github/workflows/build_nested.yml Adds nested workflow fixture.
actions/ql/test/query-tests/Security/CWE-829/9466014afba34ef28239871ceabf4132/TestOrg/TestRepo/ref-07cp61dt7qne3/.github/workflows/build_nested_branching.yml Adds branching workflow fixture.
actions/ql/test/query-tests/Security/CWE-094/CodeInjectionMedium.expected Updates medium-query results.
actions/ql/test/query-tests/Security/CWE-094/CodeInjectionCritical.expected Updates critical-query results.
actions/ql/test/query-tests/Security/CWE-094/9466014afba34ef28239871ceabf4132/ultralytics/actions/ref-07cp61dt7qne3/action.yaml Adds external action fixture.
actions/ql/test/query-tests/Security/CWE-094/9466014afba34ef28239871ceabf4132/TestOrg/TestRepo/ref-3u61h4t2rfnaf/.github/workflows/publishResults.yml Adds code-injection fixture.
actions/ql/test/query-tests/Security/CWE-094/9466014afba34ef28239871ceabf4132/TestOrg/TestRepo/ref-07cp61dt7qne3/.github/workflows/reusable-workflow.yml Adds reusable-workflow fixture.
actions/ql/test/query-tests/Security/CWE-094/9466014afba34ef28239871ceabf4132/TestOrg/TestRepo/ref-07cp61dt7qne3/.github/actions/clone-repo/action.yaml Adds composite-action fixture.
actions/ql/test/qlpack.yml Loads external models in tests.
actions/ql/test/library-tests/external-reusable-workflows/external_reusable_workflows.ql Tests workflow call resolution.
actions/ql/test/library-tests/external-reusable-workflows/external_reusable_workflows.expected Records workflow resolution results.
actions/ql/test/library-tests/external-reusable-workflows/9466014afba34ef28239871ceabf4132/TestOrg/TestRepo/ref-3tf7yq1278i0t/.github/workflows/second.yml Adds v2 callee fixture.
actions/ql/test/library-tests/external-reusable-workflows/9466014afba34ef28239871ceabf4132/TestOrg/TestRepo/ref-3tf7yq1278i0t/.github/workflows/first.yml Adds v2 nested caller fixture.
actions/ql/test/library-tests/external-reusable-workflows/9466014afba34ef28239871ceabf4132/TestOrg/TestRepo/ref-0wu7t20oora8i/.github/workflows/second.yml Adds v1 callee fixture.
actions/ql/test/library-tests/external-reusable-workflows/9466014afba34ef28239871ceabf4132/TestOrg/TestRepo/ref-0wu7t20oora8i/.github/workflows/first.yml Adds v1 nested caller fixture.
actions/ql/test/library-tests/external-reusable-workflows/9466014afba34ef28239871ceabf4132/LegacyOrg/LegacyRepo/ref-07cp61dt7qne3/.github/workflows/legacy.yml Adds unmodeled workflow fixture.
actions/ql/test/library-tests/external-reusable-workflows/.github/workflows/unmodeled_external_reusable_workflow.yml Tests unmodeled calls.
actions/ql/test/library-tests/external-reusable-workflows/.github/workflows/external_reusable_workflow.yml Tests versioned calls.
actions/ql/test/library-tests/external-composite-actions/external_composite_actions.ql Tests action call resolution.
actions/ql/test/library-tests/external-composite-actions/external_composite_actions.expected Records action resolution results.
actions/ql/test/library-tests/external-composite-actions/9466014afba34ef28239871ceabf4132/UnmodeledOrg/Actions/ref-0wu7t20oora8i/remote/action.yml Adds unmodeled action fixture.
actions/ql/test/library-tests/external-composite-actions/9466014afba34ef28239871ceabf4132/TestOrg/Actions/ref-3tf7yq1278i0t/remote/action.yml Adds v2 external action.
actions/ql/test/library-tests/external-composite-actions/9466014afba34ef28239871ceabf4132/TestOrg/Actions/ref-0wu7t20oora8i/remote/action.yml Adds v1 external action.
actions/ql/test/library-tests/external-composite-actions/.github/workflows/caller.yml Adds action caller workflow.
actions/ql/test/library-tests/external-composite-actions/.github/actions/root-v2/action.yml Adds local v2 root action.
actions/ql/test/library-tests/external-composite-actions/.github/actions/root-v1/action.yml Adds local v1 root action.
actions/ql/test/library-tests/external-composite-actions/.github/actions/leaf/action.yml Adds local leaf action.
actions/ql/test/external-reusable-workflows.model.yml Defines test download models.
actions/ql/src/change-notes/2026-07-31-external-workflow-models.md Adds analysis change note.
actions/ql/lib/ext/config/workflow_runtime_data.yml Registers extension schemas.
actions/ql/lib/codeql/actions/security/CodeInjectionQuery.qll Uses resolved workflow callers.
actions/ql/lib/codeql/actions/Helper.qll Removes legacy path exclusions.
actions/ql/lib/codeql/actions/dataflow/internal/DataFlowPrivate.qll Uses qualified callable names.
actions/ql/lib/codeql/actions/config/ConfigExtensions.qll Declares new predicates.
actions/ql/lib/codeql/actions/config/Config.qll Exposes extension data.
actions/ql/lib/codeql/actions/ast/internal/Ast.qll Resolves modeled external calls.
actions/extractor/tools/baseline-config.json Updates baseline extraction paths.
actions/extractor/tools/autobuild.sh Updates Unix path filters.
actions/extractor/tools/autobuild-impl.ps1 Updates Windows path filters.

Review details

  • Files reviewed: 35/44 changed files
  • Comments generated: 2
  • Review effort level: Balanced

JarLob added 2 commits July 31, 2026 16:48
Resolve $/ paths in downloaded reusable workflows and composite actions against their modeled repository, and cover both forms while retaining ./ compatibility.
Preserve both Actions test data extensions and regenerate the conflicting CWE-094 and CWE-829 expected results.

@github-advanced-security github-advanced-security AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

CodeQL found more than 20 potential problems in the proposed changes. Check the Files changed tab for more details.

JarLob added 2 commits July 31, 2026 17:22
Rename model-binding predicates that do not return values and replace omittable exists variables with don't-care expressions.
Add QLDoc for external workflow and composite-action model bindings, classifications, and callable-name resolution.
Comment thread actions/ql/lib/codeql/actions/ast/internal/Ast.qll Outdated
include:.github/workflows/*.yaml
include:.github/reusable_workflows/**/*.yml
include:.github/reusable_workflows/**/*.yaml
include:9466014afba34ef28239871ceabf4132/**/*.yml

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This magic number approach does not sound right to me. But I lack sufficient contextual knowledge here to suggest anything.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It is just a GUID without dashes. On one hand, especially because it becomes visible in web ui alert, it could be something human readable. On the other hand something very short such as reusable_workflow may collide with a folder in the repository. So something like downloaded_external_workflows_and_actions may work. I went with a unique GUID, but I'm open for discussions.

Comment on lines +434 to +436
externalCompositeActionDataModel(owner, repo, action_path, requested_ref, resolved_commit_sha,
local_path) and
local_path.trim() = this.getLocation().getFile().getRelativePath()

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Quick check: for tuples in externalCompositeActionDataModel is it true that there is at most one such tuple for each local_path? I.e. does the local_path uniquely determine the rest of the values? Because otherwise this looks like a massive performance pitfall, since this joins with any Locationwith a matchinggetFile`.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

local_path is not unique: the producer intentionally lets requested refs with identical content share one materialized file while retaining separate provenance rows.
However, I asked AI to check the generated evaluator plan. The current predicate scans the model rows first and then uses keyed joins through relative path, file, location, and the action AST; it does not start by enumerating every Location. I also tested a path-bound bindingset/inline_late helper, but that changed the plan to an AST-to-model Cartesian product, increased joined tuples, and showed no runtime improvement.

Comment on lines +586 to +588
externalReusableWorkflowDataModel(owner, repo, workflow_path, requested_ref,
resolved_commit_sha, local_path) and
local_path.trim() = this.getLocation().getFile().getRelativePath()

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same question applies here as the pattern is the same.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I tested this on the Grafana Actions database. All eight reusable-workflow model rows resolved to extracted workflow files, with each local_path matching the AST file’s relative path. The current plan scans externalReusableWorkflowDataModel first and uses keyed joins through file, location, and ReusableWorkflowImpl.

Comment thread actions/ql/lib/codeql/actions/ast/internal/Ast.qll
@aschackmull

Copy link
Copy Markdown
Contributor

I've commented a bit, but this really needs another set of 👀 . Also, several constructions have the looks of something that might have poor join-orders, so do check performance thoroughly.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Actions Analysis of GitHub Actions documentation

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants